package com.example.springboot1.controller;

import com.example.springboot1.Service.LoginService;
import com.example.springboot1.pojo.Login;
import com.example.springboot1.pojo.LoginVo;
import com.example.springboot1.pojo.User;
import com.example.springboot1.utils.JwtUtils;
import com.example.springboot1.utils.MD5;
import com.example.springboot1.utils.result.R;
import com.example.springboot1.utils.result.Result;
import com.google.code.kaptcha.Producer;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.web.bind.annotation.*;

import javax.imageio.ImageIO;
import javax.servlet.http.HttpServletRequest;
import java.awt.image.BufferedImage;
import java.io.ByteArrayOutputStream;
import java.io.File;
import java.io.FileOutputStream;
import java.io.OutputStream;
import java.util.Base64;
import java.util.List;
import java.util.UUID;
import java.util.concurrent.TimeUnit;

@RestController
public class LoginController {
    @Autowired
    private RedisTemplate<String, String> redisTemplate;
    @Autowired
    private Producer producer;
    @Autowired
    private LoginService loginService;
    @GetMapping("/LoginById/{id}")
    public Login getLoginById(@PathVariable("id") Integer id) {
        return loginService.getLoginById(id);
    }

    //登录
    @GetMapping("/Login/{user_name}/{user_pwd}")
    public Login findLogin(@PathVariable("user_name") String user_name,@PathVariable("user_pwd") String user_pwd) {
        return loginService.findLogin(user_name,user_pwd);
    }

    @PostMapping("/insertLogin")
    public int InsertLogin(@RequestBody Login login) {
        //MD5加密用户名密码
        String memberPass = login.getUser_pwd();
        String memberPassSecret = MD5.encrypt(memberPass);
        login.setUser_pwd(memberPassSecret);
        int i = loginService.InsertLogin(login);
        return i;
    }

    @GetMapping("/updateLogin")
    public int updateLogin(@RequestBody Login login) {
        int i = loginService.updateLogin(login);
        return i;
    }

    @GetMapping("/deleteLogin/{id}")
    public int deleteLogin(@PathVariable("id") Integer id) {
        return loginService.deleteLogin(id);
    }

    //分页
    @GetMapping("/LoginPage/{pageNum}/{pageSize}")
    public List<Login> findPage(@PathVariable("pageNum") Integer pageNum, @PathVariable("pageSize") Integer pageSize){
        pageNum = (pageNum-1);
        return loginService.LoginPage(pageNum,pageSize);
    }



    //1、登录和校验验证码
    @PostMapping("/login")
    public Result loginUser(@RequestBody LoginVo loginVo) {
        //LoginVo对象封装用户名、密码、验证码和验证码id
        //返回token值，使用jwt生成
        String token = loginService.login(loginVo);
        //校验验证码
        String code = loginVo.getCode();      //获得前台的验证码
        String codeId = loginVo.getCodeId();  //获取codeId
        //将前台的验证码转为小写
        String receivedCode = code.toLowerCase();
        //从redis中获取值
        String s = redisTemplate.opsForValue().get(codeId);
        if (receivedCode.equals(s)) {
            System.out.println("验证码正确");
            return Result.ok(token);
        }else {
            System.out.println("验证码不正确");
            return Result.fail();
        }
    }

    //2、根据token获取用户信息
    @GetMapping("getMemberInfo")
    public Result getMemberInfo(HttpServletRequest request) {
        //调用jwt工具类的方法。根据request对象获取头信息，返回用户id
        int memberId = JwtUtils.getMemberIdByJwtToken(request);
        //查询数据库根据用户id获取用户信息
        Login member = loginService.getLoginById(memberId);
        System.out.println("根据用户id获取用户信息");
        return Result.ok(member);
    }

    private static int captchaExpires = 3 * 60; //超时时间3min

    //3、获得验证码
    @GetMapping("getCaptcha")
    public R getCaptcha() {
        //生成文字验证码
        String code = producer.createText();
        System.out.println("验证码：" + code);
        // 生成图片验证码
        BufferedImage image = producer.createImage(code);
        String base64String = "";
        String codeId = "";
        try {
            // 存储到本地方便观察效果
             /*
            File file = new File("E:\\test\\" + System.currentTimeMillis() + ".PNG");
            OutputStream fos = new FileOutputStream(file);//FileOutputStream字节输出流
            */
            OutputStream fos = new FileOutputStream(new File("E:\\code\\" + System.currentTimeMillis() + ".PNG"));
            //直接返回图片
            ImageIO.write(image, "PNG", fos); //将图片写入指定文件
            //关闭管道
            fos.close();

            //将图片文件转换成Byte数组
            ByteArrayOutputStream bos = new ByteArrayOutputStream(); //ByteArrayOutputStream:对byte类型数据进⾏写⼊的类 相当于⼀个中间缓冲层
            ImageIO.write(image, "PNG", bos);
            byte[] bytes = bos.toByteArray();
            //base64编码
            Base64.Encoder encoder = Base64.getEncoder();
            base64String = "data:image/png;base64," + encoder.encodeToString(bytes);
            bos.close();
            codeId = UUID.randomUUID().toString();
            redisTemplate.opsForValue().set(codeId, code, captchaExpires, TimeUnit.SECONDS); //（key,value,时间）
        } catch (Exception e) {
            e.printStackTrace();
        }
        return R.ok().data("codeId",codeId).data("base64String",base64String);
    }

    //4、验证码校验
    @PostMapping("/checkCaptcha")
    public R getCheckCaptcha(@RequestBody LoginVo loginVo) {
        String code = loginVo.getCode();      //获得前台的验证码
        String codeId = loginVo.getCodeId();  //获取codeId
        //将前台的验证码转为小写
        String receivedCode = code.toLowerCase();
        //从redis中拿值
        String s = redisTemplate.opsForValue().get(codeId);
        if (receivedCode.equals(s)) {
            return R.ok();
        }else {
            return R.error();
        }
    }


}
